/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */
package sha.pkg1;

/**
 *
 * @author Stev
 */
public class fnApoyo {


       
 /*@ <b>creaBloque</b>
  * Entradas: @mensaje es un String
  * Salida: StringBuilder[]
  * Descripcion: Crea un arreglo de StringBuilder donde el @mensaje se subdivide en bloques
  * de largo fijo.
  */
public StringBuilder[] creaBloque(StringBuilder mensaje, int bits_bloque){
    StringBuilder temp= new StringBuilder(mensaje);
    int largo = mensaje.length();
    int num_bloques= largo/bits_bloque;
    
    if(largo%bits_bloque!=0){
      num_bloques++;
    }
  
    StringBuilder [] msje_enBloques = new StringBuilder[num_bloques];
    
    for(int i=0,j=0;i<num_bloques;i++,j=j+bits_bloque){
        
        if(largo%bits_bloque!=0 && i==num_bloques-1){
               String bloqueCojo= temp.substring(j);
                int largoCojo= bits_bloque- bloqueCojo.length();
               for(int k=0; k<largoCojo;k++){  
               bloqueCojo=bloqueCojo+"0";
               }
               msje_enBloques[i]=new StringBuilder(bloqueCojo);
        }
        else{   
            msje_enBloques[i]= new StringBuilder(temp.substring(j,j+bits_bloque));
        }
        
    }
     
    return msje_enBloques;
   
}
 
////////////////////////////////////////////////////////////////////////////////////////////////
/////////////////////////     FUNCIONES DE IMPRESION       ////////////////////////////
////////////////////////////////////////////////////////////////////////////////////////////////

 /*@ <b>Imprimir</b>
  * Entradas: @unido es un StringBuilder a imprimir, @largoBloques es el largo antes de agregar un espacio
  * Descripcion: Imprime por output agregando un spacio que se indique entre cada bloque.
  */
void imprimir(StringBuilder unido, int largoBloques){
 
    StringBuilder conEspacio = new StringBuilder(unido);
   
    for (int i=1 ; i<(unido.length()/largoBloques) ; i++){
   
        int espacio = largoBloques*i+(i-1);
        conEspacio.insert(espacio,' ');        
    }
   
System.out.println(conEspacio);
   
}

 /*@ <b>Imprimir</b>
  * Entradas: @unido es un StringBuilder a imprimir, @largoBloques es el largo antes de agregar un espacio
  * Salida: String. 
 * Descripcion: No imprime realmente, solo devuelve un string con cierta separacion indicada.
  */
public StringBuilder imprimirPantalla(StringBuilder unido, int largoBloques){
 
    StringBuilder conEspacio = new StringBuilder(unido);
   
    for (int i=1 ; i<(unido.length()/largoBloques) ; i++){
   
        int espacio = largoBloques*i+(i-1);
        conEspacio.insert(espacio,' ');        
    }
   
return conEspacio;
   
}

////////////////////////////////////////////////////////////////////////////////////////////////
/////////////////////////     OPERADORES LOGICOS      ////////////////////////////
////////////////////////////////////////////////////////////////////////////////////////////////

 /*@ <b>Realiza la operaci�n l�gica OR exclusivo sobre dos strings de igual tama�o</b>
  * Entradas: @a y @b son StringBuilders con valores binarios
  * Descripcion: Compara uno a uno los d�gitos de los arreglos, si estos son diferentes agrega un 1,
  * caso contrario, agrega 0 a un nuevo arreglo.
  */
public StringBuilder funcionXOR(StringBuilder a, StringBuilder b){
StringBuilder resultado = new StringBuilder(a);

if(a.length() == b.length()){
 
    for(int i=0; i<a.length(); i++){
       //Si son iguales concatena un 0 en el resultado
        if (a.charAt(i)== b.charAt(i)){
          resultado.setCharAt(i, '0');
       }
        //Caso contrario concatena un 1
       else{
         resultado.setCharAt(i, '1');
       }
    }
}
else{
System.out.println("Error, las entradas deben ser del mismo tama�o");
}

return resultado;
}



public StringBuilder funcionAND(StringBuilder a, StringBuilder b){
StringBuilder resultado = new StringBuilder(a);

if(a.length() == b.length()){
 
    for(int i=0; i<a.length(); i++){
       //Si alguno de los dos es 0, el resultado es 0
        if (a.charAt(i)==0 || b.charAt(i)==0){
          resultado.setCharAt(i, '0');
       }
        //Caso contrario concatena un 1
       if(a.charAt(i)==1 && b.charAt(i)==1){
         resultado.setCharAt(i, '1');
       }
    }
}
else{
System.out.println("Error, las entradas deben ser del mismo tama�o");
}

return resultado;
}

public StringBuilder funcionOR(StringBuilder a, StringBuilder b){
StringBuilder resultado = new StringBuilder(a);

if(a.length() == b.length()){
 
    for(int i=0; i<a.length(); i++){
       //Si alguno de los dos es 1, el resultado es 1
        if (a.charAt(i)==1 || b.charAt(i)==1){
          resultado.setCharAt(i, '1');
       }
        //Caso contrario concatena un 0
       else{
         resultado.setCharAt(i, '0');
       }
    }
}
else{
System.out.println("Error, las entradas deben ser del mismo tama�o");
}

return resultado;
}

public StringBuilder funcionNOT(StringBuilder a){
StringBuilder resultado = new StringBuilder(a);


    for(int i=0; i<a.length(); i++){
       //Niego resutlado, si es 0, coloco un 1
        if (a.charAt(i)==0){
          resultado.setCharAt(i, '1');
       }
        //Caso contrario, si es 1, coloco un 0
       else{
         resultado.setCharAt(i, '0');
       }
    }

return resultado;
}


////////////////////////////////////////////////////////////////////////////////////////////////
/////////////////////////     CONVERTIR ASCII-HEX-BINARIO-DECIMAL     ////////////////////////////
////////////////////////////////////////////////////////////////////////////////////////////////
 /*@ <b>aBinario</b>
  * Entradas: @mensaje es un String
 *  Salida: StringBuilder
  * Descripcion: La entrada @mensaje se transforma a binario.
  */

public StringBuilder AsciiToBinario(String mensaje){
   
  byte[] mensajeBytes = mensaje.getBytes();
  StringBuilder enBinario = new StringBuilder();
  StringBuilder impresion = new StringBuilder();
 
 
//TRANSFORMAMOS CADA CARACTER EN BLOQUES DE 8 BITS
//PARA ELLO UTILIZAMOS DIRECTAMENTE UNA FUNCION QUE TRANSFORMA EL CARACTER
//EN ASCII Y POSTERIORMENTE A BYTES (8 BITS)
 
    for (byte b : mensajeBytes){
       
        int bEntero = b;
     
            for (int i = 0; i < 8; i++){
                //si bEntero&128 == 0 concatenamos un 0, sino un 1
                enBinario.append((bEntero & 128)==0 ? 0 : 1);
                //Desplazamos un bit hacia la izquierda
                bEntero <<= 1;
            }
 
    }
   
   
  //IMPRIMIMOS LOS BLOQUES RESULTANTES
  System.out.println("'" + mensaje + "' de largo " + enBinario.length() + " en binario es:");
  imprimir(enBinario,8);
  return enBinario;

}



public String AsciiToHex(String ascii){
        StringBuilder hex = new StringBuilder();
        
        for (int i=0; i < ascii.length(); i++) {
            hex.append(Integer.toHexString(ascii.charAt(i)));
        }
        
  System.out.println("'" + ascii + "' de largo " + hex.length() + " en hex es:");
  imprimir(hex,2);
  return hex.toString();
    } 


public String DecimalToHexadecimal(String texto){  //texto en valores decimales
  int i = Integer.parseInt(texto);
  String hex = Integer.toHexString(i);
  System.out.println("Hexadecimal de "+i+  ": " + hex);
  return hex;
}


public String DecimalToBinario(String texto){  //texto en valores decimales
  int i = Integer.parseInt(texto);
  String binary = Integer.toBinaryString(i);
  System.out.println("Binario de "+i +": " + binary);
  return binary;
}

public int BinarioADecimal(String binary) {
          
     int binario= Integer.parseInt(binary);
     int resto, decimal=0, i=0;
        while (binario != 0){
           resto = binario % 10; 
           decimal = decimal + (resto * (int) Math.pow(2, i));
           i++;
           binario = binario / 10;
        }
        
      return decimal;
    
}
        
public StringBuilder DesplazaBits(StringBuilder texto, int nDesp){

    StringBuilder desplazado = new StringBuilder(texto);
    
    for(int i=1 ; i<=nDesp ; i++){
    
    char copia = desplazado.charAt(0);
    desplazado.deleteCharAt(0);

    desplazado.insert(desplazado.length(), copia);

    }
 
   return desplazado;
}
}